#include "Fase_Config.hpp"
namespace bp
{

using namespace std;

Fase_Config::Fase_Config(const char* id, configurador* config) :

	fase(id, config),
	m_ejecutandose(true),
	m_p_ancho(0),
	m_p_alto(0),
	mo_menu(0),
	mo_submenu(0),
	m_borde(10),
	m_retrato(150),
	m_recuadro(10),
	m_fondo(0),
	m_desconocido(0),
	m_fondo_menu(0),
	m_ancho_retrato(150),
	m_vigila_desp_vertical(0),
	m_menu_oculto_activo(false),
	m_continuar_juego(true)

{
	memset(m_cuadricula, 0, sizeof(m_cuadricula[0][0]) * m_ancho * m_alto);
	/*
	* MENU OCULTO
	* pw :elvirusmanda
	* Para activar el menu oculto teclear(sin las comillas y el mas): CTRL + 'elvirusmanda'
	*/
	m_clave.push_back(SDLK_e);
	m_clave.push_back(SDLK_l);
	m_clave.push_back(SDLK_v);
	m_clave.push_back(SDLK_i);
	m_clave.push_back(SDLK_r);
	m_clave.push_back(SDLK_u);
	m_clave.push_back(SDLK_s);
	m_clave.push_back(SDLK_m);
	m_clave.push_back(SDLK_a);
	m_clave.push_back(SDLK_n);
	m_clave.push_back(SDLK_d);
	m_clave.push_back(SDLK_a);

	m_configurador->m_s_menu_oculto.IrInicio();
}

bool Fase_Config::Inicializar()
{
	// Control de fotogramas por segundo
	SDL_initFramerate	( &m_manejadorImgPorSeg );
	SDL_setFramerate	( &m_manejadorImgPorSeg, m_configurador->Imagenes_por_Segundo());

	// Tipo de fuente para el titulo del menu de seleccion de Personajes
	if ((m_tx_titulo_select_personajes.CargaFuente(Paths.ObtieneRuta("FUENTE_FASE_CONFIG_TITULO"), 60)) == false) return false;
	SDL_Color colorTitulo = {72, 61, 139, 0};
	SDL_Color colorFondoTitulo = {255, 255, 255, 0};
	m_tx_titulo_select_personajes.PonerColor ( colorTitulo );
	m_tx_titulo_select_personajes.PonerColorFondo ( colorFondoTitulo );

	// Tipo de fuente para el menu oculto
	if ((m_tx_titulo_menu_oculto.CargaFuente(Paths.ObtieneRuta("FUENTE_FASE_CONFIG_TITULO_MENU_OCULTO"), 60)) == false) return false;
	colorTitulo.r = 0; colorTitulo.g = 0; colorTitulo.b = 0;
	m_tx_titulo_menu_oculto.PonerColor(colorTitulo);
	m_tx_titulo_menu_oculto.PonerColorFondo(colorFondoTitulo);    
	if ((m_tx_linea_menu_oculto.CargaFuente(Paths.ObtieneRuta("FUENTE_FASE_CONFIG_MENU_OCULTO"), 40)) == false) return false;	
	if ((m_tx_opcion_menu.CargaFuente(Paths.ObtieneRuta("FUENTE_FASE_CONFIG_MENU_OCULTO_OPC"), 40)) == false) return false;
	m_tx_linea_menu_oculto.PonerColor(colorTitulo);
	m_tx_linea_menu_oculto.PonerColorFondo(colorFondoTitulo);
	m_tx_opcion_menu.PonerColor(colorTitulo);
	m_tx_opcion_menu.PonerColorFondo(colorFondoTitulo);

	m_fondo = Imagen::Cargar(Paths.ObtieneRuta("FONDO_CONFIG"));
	if (m_fondo == 0) return false;
	m_fondo_menu = Imagen::CrearImagen(0, m_fondo->w, m_fondo->h, m_fondo);

	m_desconocido = Imagen::Cargar(Paths.ObtieneRuta("FOTO_DESCONOCIDO_CONFIG"));
	if (m_desconocido == 0) return false;

	// FULER = 0
	SDL_Surface* ImagenTemp = 0;
	ImagenTemp = Imagen::Cargar(Paths.ObtieneRuta("FOTO_FULER_CONFIG"));
	if (ImagenTemp == 0) return false;
	m_personajes.push_back(ImagenTemp);
	m_cuadricula[0][0] = 1;
	Mix_Music* MusicaTemp = 0;
	MusicaTemp = Musica::Cargar(Paths.ObtieneRuta("SONIDO_FULER_CONFIG"));
	if (MusicaTemp == 0) return false;
	m_personajes_sonido.push_back(MusicaTemp);

	// BENEDICTO = 1
	ImagenTemp = 0;
	ImagenTemp = Imagen::Cargar(Paths.ObtieneRuta("FOTO_BENEDICTO_CONFIG"));
	if (ImagenTemp == 0) return false;
	m_personajes.push_back(ImagenTemp);
	m_cuadricula[1][0] = 1;
	MusicaTemp = 0;
	MusicaTemp = Musica::Cargar(Paths.ObtieneRuta("SONIDO_BENEDICTO_CONFIG"));
	if (MusicaTemp == 0) return false;
	m_personajes_sonido.push_back(MusicaTemp);

	// ...
	ImagenTemp = 0;
	MusicaTemp = 0;
	memset(m_keys, 0, sizeof(Keys_t) * SDLMAXKEYS);
	return true;
}

void Fase_Config::Limpiar()
{
	for (vector<SDL_Surface*>::iterator it = m_personajes.begin(); it != m_personajes.end(); it++)
		SDL_FreeSurface(*it);

	if (m_fondo)
		SDL_FreeSurface(m_fondo);

	if (m_desconocido)
		SDL_FreeSurface(m_desconocido);

	if (m_fondo_menu)
		SDL_FreeSurface(m_fondo_menu);

	for (vector<Mix_Music*>::iterator it = m_personajes_sonido.begin(); it != m_personajes_sonido.end(); it++)
		Mix_FreeMusic(*it);
	
}

Fase_Config::~Fase_Config(void)
{
	Limpiar();
}

void Fase_Config::Salir()
{
	m_ejecutandose = false;
}

bool Fase_Config::Ejecutar()
{
	if ((Inicializar()) == false) return false;
	if ((Iteracion()) == false) return false;

	return m_continuar_juego;
}

bool Fase_Config::Iteracion()
{
	while ( m_ejecutandose )
	{
		
		while ( SDL_PollEvent ( &m_evento ) )
		{
			OnEvent ( &m_evento );
		}		
		GestionaMovs(m_keys);

		if ((Dibujar()) == false) return false;
		Sonar();
		memset(m_keys, 0, sizeof(Keys_t) * SDLMAXKEYS);
		SDL_framerateDelay ( &m_manejadorImgPorSeg );
	}
	Musica::Parar();
	return true;
}

bool Fase_Config::PersonajeSeleccionado()
{
	if (m_cuadricula[m_p_ancho][m_p_alto] == 1 && (m_p_ancho == 0 && m_p_alto == 0))
	{
		SDL_Rect PosInicial = {100, 400, 0, 0};		
		Color_t colorTransp = {68, 9, 123};
		m_configurador->ObtenerActor() = new ElFuler(PosInicial, perfilDer, colorTransp, Paths.ObtieneRuta("FULLER_PERFIL_DER"), Paths.ObtieneRuta("FULLER_PERFIL_IZQ"), 100);
		return true;
	}

	return false;
}


void Fase_Config::KeyDownMenuSelecPersonajes(Keys_t movs[] )
{
	if (movs[SDLK_LEFT].Press == true)
	{
		if (m_p_ancho > 0) m_p_ancho--;		
	}
	
	else if (movs[SDLK_RIGHT].Press == true)
	{
		if (m_p_ancho < m_ancho-1) m_p_ancho++;		
	}
	
	else if (movs[SDLK_UP].Press == true)
	{
		if (m_p_alto > 0)
		{
			m_p_alto--;
			m_vigila_desp_vertical = -1;
		}
	}

	else if (movs[SDLK_DOWN].Press == true)
	{
		if (m_p_alto < m_alto-1)
		{
			m_p_alto++;
			m_vigila_desp_vertical = 1;
		}
	}

	else if (movs[SDLK_SPACE].Press == true)
	{
		if (PersonajeSeleccionado() == true)					
			Salir();		
	}

	else if (movs[SDLK_ESCAPE].Press == true)
	{
		m_continuar_juego = false;
		Salir();		
	}
	else if (movs[SDLK_LCTRL].Press == true)
	{
		m_enciende_clave = true;
		return;
	}

}

void Fase_Config::KeyDownMenuOculto(Keys_t movs[]/*SDLKey sym, SDLMod , Uint16*/ )
{
	ty_m_it_menu itm;
	if (movs[SDLK_LEFT].Press == true)
		m_configurador->m_s_menu_oculto.AvanIzq();		

	else if (movs[SDLK_RIGHT].Press == true)
		m_configurador->m_s_menu_oculto.AvanDer();		

	else if (movs[SDLK_UP].Press == true)
		m_configurador->m_s_menu_oculto.AvanArriba();

	else if (movs[SDLK_DOWN].Press == true)
		m_configurador->m_s_menu_oculto.AvanAbajo();

	else if (movs[SDLK_SPACE].Press == true)
	{	
		itm = m_configurador->m_s_menu_oculto.ObtMenuActual();
		if ((*itm).second.valor.compare(m_configurador->m_activado) == 0)
			m_configurador->m_s_menu_oculto.PoneValor(m_configurador->m_desactivado);
		else
			m_configurador->m_s_menu_oculto.PoneValor(m_configurador->m_activado);
	}

	else if (movs[SDLK_ESCAPE].Press == true)
	{
		AplicaConfig();
		m_menu_oculto_activo = false;
	}  
}

void Fase_Config::GestionaMovs(Keys_t movs[])
{
	if (m_menu_oculto_activo == false)
	{
		if (m_vigila_desp_vertical != 0) return;
		KeyDownMenuSelecPersonajes(movs);
	}
	else
		KeyDownMenuOculto(movs);  
}

void Fase_Config::OnKeyDown(SDLKey sym, SDLMod , Uint16 )
{
	m_keys[sym].Press = true;
	if (m_enciende_clave == true && m_clave_entrada.size() < m_clave.size())
	{
		m_clave_entrada.push_back(sym);
	}
	if (m_enciende_clave == true && m_clave.size() == m_clave_entrada.size())
	{
		m_menu_oculto_activo = (equal(m_clave.begin(), m_clave.end(), m_clave_entrada.begin())) ? true : false;
		m_clave_entrada.clear();
		m_enciende_clave = false;
	}	
}

void Fase_Config::OnKeyUp(SDLKey sym, SDLMod , Uint16 )
{
  m_keys[sym].UnPress = true; 
}

void Fase_Config::OnEvent ( SDL_Event* evento )
{
	Eventos::OnEvent ( evento );
}

void Fase_Config::AplicaConfig()
{
	ty_m_it_menu itm = m_configurador->m_s_menu_oculto.ObtMenu(make_pair("ROOT1", 0));
	if (itm != m_configurador->m_s_menu_oculto.Fin())
	{
		if ((*itm).second.valor.compare(m_configurador->m_activado) == 0)
		{
			    // RE-CONFG SISTEMA : VIDEO
				if ( ( m_configurador->Escenario() = SDL_SetVideoMode ( m_configurador->Pantalla_Ancho(), m_configurador->Pantalla_Alto(), m_configurador->Pantalla_Profundidad(), SDL_HWSURFACE | SDL_DOUBLEBUF | SDL_FULLSCREEN ) ) == 0 )
				{
					 SDL_SetError(SDL_GetError()); 
				}
		}
		else
		{
				// RE-CONFG SISTEMA : VIDEO
				if ( ( m_configurador->Escenario() = SDL_SetVideoMode ( m_configurador->Pantalla_Ancho(), m_configurador->Pantalla_Alto(), m_configurador->Pantalla_Profundidad(), SDL_HWSURFACE | SDL_DOUBLEBUF ) ) == 0 )
				{
					 SDL_SetError(SDL_GetError()); 
				}
		}
	}
}

bool Fase_Config::Sonar()
{
	static bool fuler_suena = false, benedicto_suena = false;

	if (m_p_ancho == 0 && m_p_alto == 0)
	{
		if ( Musica::EstaSonado() == false )
		{
			Musica::Sonar(m_personajes_sonido.at(fuler));
			fuler_suena = true;
			benedicto_suena = false;
		}
		else if (fuler_suena == false)
		{
			Musica::Parar();
		}
	}
	else if (m_p_ancho == 1 && m_p_alto == 0)
	{
		if ( Musica::EstaSonado() == false )
		{
			Musica::Sonar(m_personajes_sonido.at(benedicto));
			benedicto_suena = true;
			fuler_suena = false;
		}
		else if (benedicto_suena == false)
		{
			Musica::Parar();
		}
	}
	else
	{
		fuler_suena = false;
		benedicto_suena = false;
		Musica::Parar();
	}

	return true;
}


void Fase_Config::DibujarMenuOculto(SDL_Surface* ImagenDestino)
{

	Uint32 			colorBorde 			= SDL_MapRGB (ImagenDestino->format, 0, 0, 0 );
	Uint32 			colorFondo 			= SDL_MapRGB (ImagenDestino->format, 255, 255, 255 );
	int32_t				alto_menu 			= 500;
	int32_t				ancho_menu 			= 700;
	int32_t				marjenRectX			= (ImagenDestino->w-ancho_menu)/2;
	int32_t				marjenRecty			= ImagenDestino->h-alto_menu-10;
	SDL_Surface*	TextoImagen 		= 0;   
	int32_t				y					= 0;

	Imagen::LimpiarImagen(ImagenDestino);
	TextoImagen = Imagen::CrearImagen(0, 490, 200, m_configurador->Escenario());
	Imagen::LimpiarImagen(TextoImagen);		
	ty_m_it_menu itm = m_configurador->m_s_menu_oculto.Iterar();
	do
	{
		SDL_Color colorTitulo = {0, 0, 0, 0};
		if (m_configurador->m_s_menu_oculto.EsLaActual(itm))					
			colorTitulo.r = 165; colorTitulo.g = 42; colorTitulo.b = 42;

		m_tx_linea_menu_oculto.PonerColor(colorTitulo);
		SDL_Surface*	LineaImagen		= 0; 
		SDL_Surface*	OpcionImagen	= 0;
		LineaImagen = m_tx_linea_menu_oculto.Dibujar((*itm).second.titulo.c_str());
		Imagen::Dibujar(TextoImagen, LineaImagen, 0, y, 0, 0, LineaImagen->w, LineaImagen->h );	
		SDL_FreeSurface(LineaImagen);

		if ((*itm).second.esDirectorio == false)
		{
			OpcionImagen = m_tx_opcion_menu.Dibujar((*itm).second.valor.c_str());
			Imagen::Dibujar(TextoImagen, OpcionImagen, TextoImagen->w-OpcionImagen->w, y, 0, 0, OpcionImagen->w, OpcionImagen->h );	
			SDL_FreeSurface(OpcionImagen);
		}
		y += 40;							
		itm = m_configurador->m_s_menu_oculto.Iterar();
	} while( itm != m_configurador->m_s_menu_oculto.Fin());

	Imagen::DibujarRectangulo(ImagenDestino, (ImagenDestino->w-ancho_menu)/2 , ImagenDestino->h-alto_menu-10, ancho_menu, alto_menu, colorBorde);
	Imagen::DibujarRectangulo(ImagenDestino, ((ImagenDestino->w-ancho_menu)/2)+1 , ImagenDestino->h-alto_menu-9, ancho_menu-2, alto_menu-2, colorFondo);		
	Imagen::Dibujar(ImagenDestino, TextoImagen, marjenRectX+60, marjenRecty+100, 0, 0, TextoImagen->w, TextoImagen->h);	



	SDL_Surface*	LineaImagen		= 0;
	LineaImagen = m_tx_titulo_menu_oculto.Dibujar("Menu Oculto [ACTIVO]");
	Imagen::Dibujar(ImagenDestino, LineaImagen, (ImagenDestino->w-LineaImagen->w)/2, 10, 0, 0, LineaImagen->w, LineaImagen->h );
	SDL_FreeSurface(LineaImagen);

	SDL_FreeSurface(TextoImagen);
}


void Fase_Config::DibujarPersonajes(SDL_Surface* ImagenDestino)
{
	int32_t 	inicio_x		= ( ImagenDestino->w - ((m_recuadro * 8) + (m_ancho_retrato * m_ancho)) ) / 2;
	int32_t 	inicio_y 		= 200;
	int32_t 	desplazamiento_x        = 0;
	int32_t 	desplazamiento_y        = 0;
	Uint32 	colorSeleccion 		= SDL_MapRGB (ImagenDestino->format, 220, 20, 60 );
	int32_t 	len_recuadro 		= m_retrato + (m_recuadro * 2);


	for (size_t alto = 0; alto < m_alto; alto++)
	{
		desplazamiento_x = inicio_x;
		desplazamiento_y += (alto == 0) ? inicio_y + m_recuadro : m_ancho_retrato + (m_recuadro * 3);
		for (size_t ancho = 0; ancho < m_ancho; ancho++)
		{
			desplazamiento_x += (ancho == 0) ? m_recuadro : m_ancho_retrato + (m_recuadro * 3);

			if ( ancho == m_p_ancho && alto == m_p_alto)
			{
				Imagen::DibujarRectangulo(ImagenDestino, desplazamiento_x , desplazamiento_y, len_recuadro, len_recuadro, colorSeleccion);
			}

			Imagen::Dibujar(ImagenDestino, m_desconocido, desplazamiento_x + m_recuadro,  desplazamiento_y + m_recuadro, 0, 0, m_desconocido->w,  m_desconocido->h );

			if (m_cuadricula[ancho][alto] == 1)
			{
				Imagen::Dibujar(ImagenDestino, m_personajes.at(ancho + alto), desplazamiento_x + m_recuadro,  desplazamiento_y + m_recuadro, 0, 0, m_personajes.at(ancho + alto)->w,  m_personajes.at(ancho + alto)->h );
			}
		}
	}
}


bool Fase_Config::Dibujar()
{
	if (m_menu_oculto_activo == false)
	{
		MenuSelecPersonajes(m_configurador->Escenario());
		TextoMenuPersonajes(m_configurador->Escenario());
	}
	else
	{
		DibujarMenuOculto(m_configurador->Escenario());
	}
	SDL_Flip ( m_configurador->Escenario() );
	return true;
}

void Fase_Config::TextoMenuPersonajes(SDL_Surface* ImagenDestino)
{
	SDL_Surface* TextoImagen = 0;
	TextoImagen = m_tx_titulo_select_personajes.Dibujar("Seleccione Jugador");
	Imagen::CrearTransparencia(TextoImagen, 255, 255, 255);
	Imagen::Dibujar (ImagenDestino, TextoImagen, (ImagenDestino->w - TextoImagen->w) / 2, 5, 0, 0, TextoImagen->w, TextoImagen->h );
	SDL_FreeSurface(TextoImagen);
}


void Fase_Config::MenuSelecPersonajes(SDL_Surface* ImagenDestino)
{
	static bool 	EnDesplazamiento 			= false;
	static int32_t  	Desplazamiento_x			= (m_fondo->w - ImagenDestino->w) / 2;
	static int32_t  	Desplazamiento_y			= 50;
	static int32_t  	Desplazamiento_y_tope		= 0;

	Imagen::LimpiarImagen(ImagenDestino);

	if (m_vigila_desp_vertical != 0)
	{
		if (EnDesplazamiento == false)
		{

			Imagen::Dibujar(m_fondo_menu, m_fondo);
			DibujarPersonajes(m_fondo_menu);
			EnDesplazamiento = true;
			if (m_vigila_desp_vertical == 1)
				Desplazamiento_y_tope = Desplazamiento_y + m_ancho_retrato;
			else if (m_vigila_desp_vertical == -1)
				Desplazamiento_y_tope = Desplazamiento_y - m_ancho_retrato;
		}
		else
		{
			if (m_vigila_desp_vertical == 1)
			{
				if (Desplazamiento_y < Desplazamiento_y_tope)
					Desplazamiento_y+=3;
				else if (Desplazamiento_y == Desplazamiento_y_tope)
				{
					m_vigila_desp_vertical = 0;
					EnDesplazamiento = false;
				}
			}
			else if (m_vigila_desp_vertical == -1)
			{
				if (Desplazamiento_y > Desplazamiento_y_tope)
					Desplazamiento_y-=3;
				else if (Desplazamiento_y == Desplazamiento_y_tope)
				{
					m_vigila_desp_vertical = 0;
					EnDesplazamiento = false;
				}
			}
		}
	}
	else
	{
		Imagen::Dibujar(m_fondo_menu, m_fondo);
		DibujarPersonajes(m_fondo_menu);
	}
	Imagen::Dibujar(ImagenDestino, m_fondo_menu, 0, 0, Desplazamiento_x, Desplazamiento_y, ImagenDestino->w, ImagenDestino->h);

}



} // namespace bp
